/*************************************************************************
	> File Name: ping.h
	> Author: 
	> Mail: 
	> Created Time: 2015年04月23日 星期四 15时09分01秒
 ************************************************************************/

#ifndef _PING_H
#define _PING_H

#define ICMP_ECHOREPLY 0 /*echo 应答*/
#define ICMP_ECHO 8 /*echo 请求*/

#define BUFFSIZE 1500 /*发送缓存最大值*/
#define DEFAULT_LEN 56 /*ping消息数据默认大小*/

/*数据类型别名*/
typedef unsigned char u8;
typedef unsigned short u16;
typedef unsigned int u32;


/*ICMP 消息头部*/
struct icmphdr{
    u8 type;
    u8 code;
    u16 checksum;
    union{
        struct {
            u16 id;
            u16 sequence;
        }echo;
        u32 gateway;
        struct {
            u16 unused;
            u16 mtu;
        }frag;  /*pmtu发现*/
    }un;
    /*icmp 数据占位符*/
    u8 data[0];
#define icmp_id un.echo.id
#define icmp_seq un.echo.sequence
};
#define ICMP_HSIZE sizeof(struct icmphdr)


struct iphdr{
    u8 hlen:4,ver:4;/*hlen:首部长度，ver:版本号*/
    u8 tos;/*服务类型*/
    u16 tot_len;/*总长度（字节数）*/
    u16 id;/*标识*/
    u16 frag_off;/*3位标志+13位片内偏移*/
    u8 ttl;/*生存时间戳*/
    u8 protocol;/*协议*/
    u16 check;/*校验和*/
    u32 saddr;/*源地址*/
    u32 daddr;/*目的地址*/
};

char *hostname; /*被ping的主机*/
int datalen = DEFAULT_LEN;/*ICMP消息携带的数据长度*/
char sendbuf[BUFFSIZE];
char recvbuf[BUFFSIZE];

int nsent;/*发送的ICMP消息序号*/
int nrecv;

pid_t pid;/*ping程序的进程PID*/
struct timeval recvtime;/*收到ICMP应答的事件戳*/
int sockfd;/*发送和接受原始套接字*/
struct sockaddr_in dest;/*被ping主机ip地址*/
struct sockaddr_in from;/*发送ping应答xiaoxi的主机地址*/
struct sigaction act_alarm;
struct sigaction act_int;

/*函数原型*/
void alarm_handler(int);/*SIGALRM处理程序*/
void int_handler(int);/*SIGINT处理程序*/
void set_sighandler();/*设置信号处理程序*/
void send_ping();/*发送ping消息*/
void recv_reply();/*接收ping应答*/
u16 checksum(u8 *buf,int len);/*计算校验和*/
int handle_pkt();/*icmp 应答消息处理*/
void get_statistics(int,int);/*统计ping命令的检测结果*/
void bail(const char *);/*报告错误*/


#endif
